/* 
 * The MIT License
 *
 * Copyright 2014 Venkat Ram Akkineni.
 *
 * Permission is hereby granted, free of charge, to any person obtaining a copy
 * of this software and associated documentation files (the "Software"), to deal
 * in the Software without restriction, including without limitation the rights
 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
 * copies of the Software, and to permit persons to whom the Software is
 * furnished to do so, subject to the following conditions:
 *
 * The above copyright notice and this permission notice shall be included in
 * all copies or substantial portions of the Software.
 *
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
 * THE SOFTWARE.
 */
package org.netbeans.modules.tfsnb.core;

import java.awt.Image;
import java.awt.event.ActionEvent;
import java.beans.PropertyChangeEvent;
import java.beans.PropertyChangeListener;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.Map.Entry;
import java.util.concurrent.ConcurrentHashMap;
import javax.swing.AbstractAction;
import javax.swing.Action;
import org.netbeans.api.core.ide.ServicesTabNodeRegistration;
import org.openide.DialogDescriptor;
import org.openide.DialogDisplayer;
import org.openide.nodes.AbstractNode;
import org.openide.nodes.Children;
import org.openide.nodes.Node;
import org.openide.util.ImageUtilities;
import org.openide.util.NbBundle;

/**
 *
 * @author Venkat Ram Akkineni
 */
public class TFSRootNode extends AbstractNode implements PropertyChangeListener {
    
    private static Node instance;   
    private static TFSRootNode defaultInstance;
    private static final Object LOCK_INIT = new Object();    
    private static TFSServerConnectionNodeFactory connections;

    public TFSRootNode() {        
        super(connections);        
        instance = this;
        TFSConnectionRegistry.getInstance().addPropertyChangeListener(this);
    }
    
    public TFSRootNode(Children children) {
        super(children);        
    }
    
    @ServicesTabNodeRegistration(
        name="tfs",                                                                 // NOI18N
        displayName="org.netbeans.modules.tfsnb.core.Bundle#TFSRootNode.LBL_TFSNode", // NOI18N
        iconResource="org/netbeans/modules/tfsnb/core/netbeans-tfs-16x16.png",       // NOI18N
        position=700
    )
    public static TFSRootNode getDefault() {
        synchronized(LOCK_INIT) {
            if (defaultInstance == null) {
                connections = new TFSServerConnectionNodeFactory();
                defaultInstance = new TFSRootNode();
            }
            return defaultInstance;
        }
    }

    @Override
    public Image getIcon(int type) {
        return ImageUtilities.loadImage("org/netbeans/modules/tfsnb/core/netbeans-tfs-16x16.png");
    }
       
    @Override
    public Image getOpenedIcon(int type) {
        return getIcon(type); 
    }

    @Override
    public boolean canRename() {
        return true; 
    }

    @Override
    public String getHtmlDisplayName() {
        return NbBundle.getMessage(TFSRootNode.class, "TFSRootNode.LBL_TFSNode");
    }
      
    
    
    @Override
    public Action[] getActions(boolean context) {
        TFSRootNode that = this;
        return new Action[] {
            new AbstractAction(NbBundle.getMessage(TFSRootNode.class, "TFSRootNode.LBL_AddConnection")) { // NOI18N
                @Override
                public void actionPerformed(ActionEvent e) {
                    AddTFSConnectionPanel panel = new AddTFSConnectionPanel(false);
                    DialogDescriptor dd = new DialogDescriptor(panel, NbBundle.getMessage(TFSRootNode.class, "TFSRootNode.LBL_AddConnection"));                    
                    DialogDisplayer.getDefault().notify(dd);
                    if(dd.getValue() == DialogDescriptor.OK_OPTION) {
                        panel.okButtonPressed();
                    } 
                }
            }
        };
    }

    @Override
    public void propertyChange(PropertyChangeEvent evt) {
        connections.refreshList((ConcurrentHashMap<String, ConnectionSettings>) evt.getNewValue());
    }

    private static class TFSServerConnectionNodeFactory extends Children.Keys<ConnectionSettings> {

        public TFSServerConnectionNodeFactory() {
        }

        @Override
        protected Node[] createNodes(ConnectionSettings key) {
            ConcurrentHashMap<String, ConnectionSettings> conns = TFSConnectionRegistry.getInstance().retrieveConnections();
            
            Node[] nodes = new Node[conns.size()];
            int i = 0;
            for(Entry entry: conns.entrySet()) {
                nodes[i] = new TFSConnectionNode((ConnectionSettings) entry.getValue());
                i++;
            }            
                        
            return nodes;
        }
        
        public void refreshList(List<ConnectionSettings> settings) {
            setKeys(settings);
        }
        
        public void refreshList(ConcurrentHashMap<String, ConnectionSettings> settings) {            
            setKeys(settings.values());
        }
        
        
    }
    
}
